package model;

import Audio.AudioCapture;
import Network.ThreadServerUDP;
import chataudio.Constant;
import controleur.AbstractChatControleur;
import java.io.Serializable;
import java.net.Inet4Address;
import java.net.InetAddress;
import java.net.SocketException;
import java.net.UnknownHostException;


/**
 * La classe Connection gère les connexions <br>
 * @author Romain Bustos
 * @author Matthieu Perrin
 * @version 1.0
 */
public class Connection extends AbstractConnection implements Serializable {
//public class Connection{
    private long ID = 0;
    private String name = null;
    private String user;
    private String setting1 = null;
    private Constant.Status State = null;
    private InetAddress adresse;
    private AudioCapture capture;
    private ThreadServerUDP lecteur;
    private boolean client = true;
    private soundSetting sound;
    private int portRecptionUDP = 2500;
    private int portEnvoieUDP = 2500;
 
    /**
    *<b>Constructeur Connection</b>
    */
    public Connection(long cID, String cname, String user) throws UnknownHostException{
        super();
        this.name = cname;
        this.user = user;
        this.ID = cID;
        this.adresse = Inet4Address.getByName(cname);
        this.sound = controleur.getLocalSoundSetting();
        this.portEnvoieUDP = controleur.getPortUDP();
        System.out.println("1Conection constructor (sans status): ADDR=" + adresse + " ID=" + ID + "NOM: " + user );
    }

    public Connection(long cID, String cname, String user, AbstractChatControleur controleur) throws UnknownHostException{
        super(controleur);
        this.name = cname;
        this.user = user;
        this.ID = cID;
        this.sound = controleur.getLocalSoundSetting();
        this.portEnvoieUDP = controleur.getPortUDP();
        this.adresse = Inet4Address.getByName(cname);
        System.out.println("3Conection constructor (param + controleur) : ADDR=" + adresse + " ID=" + ID + "NOM: " + user );
    }
   
    public Connection(Connection connection, AbstractChatControleur controleur) throws UnknownHostException{
        super(controleur);
        this.State = connection.getState();
        this.name = connection.getName();
        this.user = connection.getUser();
        this.ID = connection.getID();
        this.sound = connection.sound;
        this.portRecptionUDP = connection.portEnvoieUDP;
        this.portEnvoieUDP = controleur.getPortUDP();
        this.adresse = Inet4Address.getByName(connection.getName());
        System.out.println("4Conection constructor(Connection + Controleur) : ADDR=" + adresse + " ID=" + ID + "NOM: " + user );
    }
    
    /**
    *Modifi le caractéristiques du son
    * @param sound 
    */
    public void setSound(soundSetting sound) {
        this.sound = sound;
    }
    
    
    /**
    *permet de récupérer le nom d'utilisateur del  a connexion
    * @return user
    */
    public String getUser() {
        return user;
    }

    /**
    *permet de modifier le nom d'utilisateur de la connexion
    * @param user 
    */
    public void setUser(String user) {
        this.user = user;
    }
    
    /**
    *permet d'obtenir l'ID de la connexion
    * @return ID
    */
    public long getID() {
        return ID;
    }

    /**
    *permet d'obtenir le nom canonique de la connexion
    * C'est l'adresse IP
    * @return name
    */
    public String getName() {
        return name;
    }

    /**
    *permet de modifier l'ID de la connexion
    * @param ID 
    */
    public void setID(long ID) {
        this.ID = ID;
    }

    /**
    *permet de modifier le nom canonique de la connexion
    * C'est l'adresse IP
    * @param name 
    */
    public void setName(String name) {
        this.name = name;
    }

    /** 
    *permet d'otenir l'état de la connexion
    * @return State
    */
    public Constant.Status getState() {
        return State;
    }

    /**
    *permet de modifier l'état de la connexion
    * @param State 
    */
    public void setState(Constant.Status State) {
        this.State = State;
    }
    
    @Override
    public String toString() {
        return " ID: " + ID + " name=" + name + " State=" + State + "nom = " + user + "controleur: " +controleur ;
    } 
    
    /**
    *permet de modifier l'adresse de la connexion
    *@param host 
    */
    public void setAdresse(String host) throws UnknownHostException 
    {
        this.adresse.getByName(host);
    }
    
    /**
    *permet de modifier l'adresse de la connexion
    * @param ip 
    */
    public void setAdresse(InetAddress ip) throws UnknownHostException 
    {
        this.adresse = ip;
    }
    
    
    public InetAddress getAdresse(){
        return adresse;
    }

    public int getportEnvoieUDP() {
        return portEnvoieUDP;
    }

    public void setportEnvoieUDP(int portUDP) {
        this.portEnvoieUDP = portUDP;
    }
    
    public int getportRecptionUDP() {
        return portRecptionUDP;
    }

    public void setportRecptionUDP(int portUDP) {
        this.portRecptionUDP = portUDP;
    }
    
    public void pause(){
        lecteur.pause();
    }
    
    /**
    *<b>Methode start</b>
    * Demmarre la session audio
    */
    public void start() throws SocketException, UnknownHostException{
        System.out.println(controleur);
        //capture = new AudioCapture(adresse.getHostAddress(), Constant.udpPort, controleur);
        capture = new AudioCapture(adresse.getHostAddress(), portEnvoieUDP, controleur, sound.getFormat());
        lecteur = new ThreadServerUDP(sound.getFormat(), portRecptionUDP);
        lecteur.start();
    }
    
    /**
    *<b>Methode start</b>
    * Stop la session audio
    */
    public void stop(){
        capture.Stop();
        lecteur.arret();
        System.out.println("STOP conection");
        
        capture = null; // ne pas passer d'objet non serialisable par le reseau
        lecteur = null; // ne pas passer d'objet non serialisable par le reseau
    }

    /*
    public boolean isClient() {
        return client;
    }

    public void setServer() {
        this.client = false;
    }
*/
    
    public void setControleur(AbstractChatControleur controleur) {
        this.controleur = controleur;
    }
    
    
}
